﻿package com.gengine.manager
{
    import com.gengine.core.*;
    import flash.events.*;
    import flash.net.*;
    import flash.system.*;
    import flash.utils.*;

    public class CacheManager extends Singleton
    {
        private var _sharedObject:SharedObject;
        private const NeedSpace:int = 3.14573e+007;
        private var _versionData:Object;
        private var _memoryData:Object;
        private const CacheName:String = "hyCache";
        private const CachePath:String = "/hy/hyCache";
        private var _isCache:Boolean = false;
        private const Delay:int = 500;
        private var _saveTimer:Timer;
        private var _saveList:Array;
        private var localObject:Object;
        private var _writeNum:int = 0;
        private static var _instance:CacheManager;

        public function CacheManager()
        {
            this._versionData = {};
            this._memoryData = {};
            this._saveList = [];
            return;
        }// end function

        public function get isCache() : Boolean
        {
            return this._isCache;
        }// end function

        public function setLocalCache() : void
        {
            this.initCache();
            this.setCache(true);
            return;
        }// end function

        private function setCache(param1:Boolean) : void
        {
            var state:String;
            var value:* = param1;
            this.getSharedObject();
            if (this._sharedObject)
            {
                try
                {
                    this._sharedObject.addEventListener(NetStatusEvent.NET_STATUS, this.onNetStatusEvent);
                    state = this._sharedObject.flush(this.NeedSpace);
                    if (state != SharedObjectFlushStatus.PENDING)
                    {
                        this._sharedObject.data["isCache"] = true;
                        this._isCache = true;
                    }
                    else
                    {
                        this._sharedObject.data["isCache"] = false;
                        this._isCache = false;
                    }
                }
                catch (e:Error)
                {
                    _isCache = false;
                    Security.showSettings(SecurityPanel.LOCAL_STORAGE);
                }
            }
            return;
        }// end function

        private function getSharedObject() : SharedObject
        {
            if (this._sharedObject == null)
            {
                try
                {
                    this._sharedObject = this.getLocal(this.CachePath);
                    this._versionData = this._sharedObject.data[this.CacheName];
                    this._isCache = this._sharedObject.data["isCache"];
                }
                catch (e:Error)
                {
                    _isCache = false;
                }
                if (this._versionData == null)
                {
                    this._versionData = {};
                }
            }
            return this._sharedObject;
        }// end function

        public function initCache() : void
        {
            this.getSharedObject();
            if (this._saveTimer == null)
            {
                this._saveTimer = new Timer(this.Delay);
                this._saveTimer.addEventListener(TimerEvent.TIMER, this.onTimerHandler);
            }
            return;
        }// end function

        public function getLocal(param1:String, param2:String = null, param3:Boolean = false) : SharedObject
        {
            return SharedObject.getLocal(param1, "/", param3);
        }// end function

        private function onTimerHandler(event:TimerEvent) : void
        {
            var _loc_2:Object = null;
            if (this._saveList.length > 0)
            {
                _loc_2 = this._saveList.shift();
                if (this.writeFile(_loc_2.n, _loc_2.data, _loc_2.path) == false)
                {
                    this.deleteVersion(_loc_2.n);
                }
                else
                {
                    this.setVersion(_loc_2.n, _loc_2.v);
                    var _loc_3:String = this;
                    var _loc_4:* = this._writeNum + 1;
                    _loc_3._writeNum = _loc_4;
                }
            }
            else if (this._saveTimer.running)
            {
                this._saveTimer.stop();
            }
            return;
        }// end function

        public function setVersion(param1:String, param2:String) : void
        {
            this._versionData[param1] = param2;
            if (this._sharedObject)
            {
                this._sharedObject.data[this.CacheName] = this._versionData;
            }
            return;
        }// end function

        private function getVersion(param1:String) : String
        {
            return this._versionData[param1];
        }// end function

        public function deleteVersion(param1:String) : void
        {
            delete this._versionData[param1];
            if (this._sharedObject)
            {
                this._sharedObject.data[this.CacheName] = this._versionData;
            }
            return;
        }// end function

        public function readObject(param1:String, param2:String, param3:String = null) : Object
        {
            var _loc_4:String = null;
            if (this._isCache)
            {
                _loc_4 = this.getVersion(param1);
                if (_loc_4 == param2)
                {
                    return this.readFile(param1, param3);
                }
                return null;
            }
            return null;
        }// end function

        public function writeObject(param1:String, param2:String, param3:Object, param4:String = null) : void
        {
            if (this._isCache)
            {
                this._saveList.push({n:param1, v:param2, data:param3, path:param4});
                this.startTimer();
            }
            return;
        }// end function

        private function startTimer() : void
        {
            if (this._saveTimer.running == false)
            {
                this._saveTimer.start();
            }
            return;
        }// end function

        private function writeMemory(param1:String, param2:Object) : void
        {
            this._memoryData[param1] = param2;
            return;
        }// end function

        private function readMemory(param1:String) : Object
        {
            return this._memoryData[param1];
        }// end function

        private function deleteMemory(param1:String) : void
        {
            delete this._memoryData[param1];
            return;
        }// end function

        private function readFile(param1:String, param2:String = null) : Object
        {
            var _loc_3:SharedObject = null;
            var _loc_4:Object = null;
            if (param2 == null)
            {
                param2 = param1;
            }
            try
            {
                _loc_3 = this.getLocal(param2);
                _loc_4 = _loc_3.data[param1];
                return _loc_4;
            }
            catch (e:Error)
            {
            }
            return null;
        }// end function

        private function writeFile(param1:String, param2:Object, param3:String = null) : Boolean
        {
            var _loc_4:SharedObject = null;
            if (param2 == null)
            {
                return false;
            }
            if (param3 == null)
            {
                param3 = param1;
            }
            try
            {
                _loc_4 = this.getLocal(param3);
                _loc_4.data[param1] = param2;
                return true;
            }
            catch (e:Error)
            {
            }
            return false;
        }// end function

        public function clear() : void
        {
            this._saveList.length = 0;
            this._memoryData = {};
            this._versionData = {};
            this._sharedObject.data[this.CacheName] = this._versionData;
            this._sharedObject.flush();
            this._saveTimer.stop();
            return;
        }// end function

        private function onNetStatusEvent(event:NetStatusEvent) : void
        {
            if (event.info.code == "SharedObject.Flush.Failed")
            {
                this._isCache = false;
                this.clear();
            }
            else
            {
                this._sharedObject.removeEventListener(NetStatusEvent.NET_STATUS, this.onNetStatusEvent);
                this._isCache = true;
            }
            this._sharedObject.data["isCache"] = this._isCache;
            return;
        }// end function

        public function flush() : void
        {
            if (this._isCache && this._writeNum > 0)
            {
                this._writeNum = 0;
                if (this._sharedObject)
                {
                    this._sharedObject.flush();
                }
            }
            return;
        }// end function

        public static function get instance() : CacheManager
        {
            if (_instance == null)
            {
                _instance = new CacheManager;
            }
            return _instance;
        }// end function

    }
}
